package la.bbs558.service.impl;

import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.lang.Snowflake;
import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.getui.push.v2.sdk.ApiHelper;
import com.getui.push.v2.sdk.GtApiConfiguration;
import com.getui.push.v2.sdk.api.PushApi;
import com.getui.push.v2.sdk.dto.req.Audience;
import com.getui.push.v2.sdk.dto.req.Settings;
import com.getui.push.v2.sdk.dto.req.message.PushDTO;
import com.getui.push.v2.sdk.dto.req.message.PushMessage;
import la.bbs558.dao.UserPushDao;
import la.bbs558.entity.UserPush;
import la.bbs558.service.UserPushService;
import la.bbs558.util.Strings;
import org.springframework.stereotype.Service;

import javax.annotation.PostConstruct;
import javax.annotation.Resource;
import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * (UserPush)表服务实现类
 *
 * @author Shanks
 * @since 2024-01-20 18:16:10
 */
@Service("userPushService")
public class UserPushServiceImpl extends ServiceImpl<UserPushDao, UserPush> implements UserPushService {

    @Resource
    private UserPushDao userPushDao;

    @Resource
    private Snowflake snowflake;

    private PushApi pushApi;

    @PostConstruct
    public void createPushApi() {
        GtApiConfiguration apiConfiguration = new GtApiConfiguration();
        apiConfiguration.setAppId("uVcpdcrv0G8W1AQ0W6TH05");
        apiConfiguration.setAppKey("whsnFXmiHA8QuXfE6TOoQ5");
        apiConfiguration.setMasterSecret("bzdHGV6xBB6cro9458e7B8");
        apiConfiguration.setDomain("https://restapi.getui.com/v2/");
        // 实例化ApiHelper对象，用于创建接口对象
        ApiHelper apiHelper = ApiHelper.build(apiConfiguration);
        // 创建对象，建议复用。目前有PushApi、StatisticApi、UserApi
        pushApi = apiHelper.creatApi(PushApi.class);
    }

    @Override
    public void addPushInfo(UserPush userPush) {
        if (Strings.isEmpty(userPush.getCid())) return;
        userPush.setId(snowflake.nextId());
        int count = userPushDao.insertIgnore(userPush);
        if (count == 0) {
            // 目前是一对一
            lambdaUpdate().set(UserPush::getCid, userPush.getCid())
                    .set(UserPush::getUpdateTime, new Date())
                    .eq(UserPush::getUserId, userPush.getUserId())
                    .update();
        }
    }

    @Override
    public void pushMessage(Long toUser, Map<String, Object> msg) {
        // 查询该用户的所有cid
        List<UserPush> list = lambdaQuery()
                .select(UserPush::getCid)
                .eq(UserPush::getUserId, toUser)
                .list();
        if (CollectionUtil.isEmpty(list)) return;
        List<String> cidList = list.stream().map(UserPush::getCid).collect(Collectors.toList());
        sendMessage(cidList, msg);
    }

    private void sendMessage(List<String> cidList, Map<String, Object> msg) {
        //根据cid进行单推
        PushDTO<Audience> pushDTO = new PushDTO<>();
        // 设置推送参数，requestid需要每次变化唯一
        pushDTO.setRequestId(System.currentTimeMillis() + "");
        Settings settings = new Settings();
        pushDTO.setSettings(settings);
        //在线走个推通道时推送的消息体
        PushMessage pushMessage = new PushMessage();
        pushDTO.setPushMessage(pushMessage);
        //此格式的透传消息由 unipush 做了特殊处理，会自动展示通知栏。开发者也可自定义其它格式，在客户端自己处理。
        pushMessage.setTransmission("{payload:" + JSON.toJSONString(msg) + "}");
        // 设置接收人信息
        Audience audience = new Audience();
        pushDTO.setAudience(audience);
        cidList.forEach(audience::addCid);
        /**
         //设置离线推送时的消息体
         PushChannel pushChannel = new PushChannel();
         //安卓离线厂商通道推送的消息体
         AndroidDTO androidDTO = new AndroidDTO();
         Ups ups = new Ups();
         ThirdNotification thirdNotification = new ThirdNotification();
         ups.setNotification(thirdNotification);
         thirdNotification.setTitle("安卓离线展示的标题");
         thirdNotification.setBody("安卓离线展示的内容");
         thirdNotification.setClickType("intent");
         //注意：intent参数必须按下方文档（特殊参数说明）要求的固定格式传值，intent错误会导致客户端无法收到消息
         thirdNotification.setIntent("请填写固定格式的intent");
         androidDTO.setUps(ups);
         pushChannel.setAndroid(androidDTO);

         //ios离线apn通道推送的消息体
         Alert alert = new Alert();
         alert.setTitle("苹果离线通知栏标题");
         alert.setBody("苹果离线通知栏内容");
         Aps aps = new Aps();
         aps.setContentAvailable(0);
         aps.setSound("default");
         aps.setAlert(alert);
         IosDTO iosDTO = new IosDTO();
         iosDTO.setAps(aps);
         iosDTO.setType("notify");
         pushChannel.setIos(iosDTO);

         pushDTO.setPushChannel(pushChannel);
         */

        // 进行cid单推
        pushApi.pushToSingleByCid(pushDTO);
    }
}

